package com.tlgen.service.impl;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.tlgen.Model.ConfigServer;
import com.tlgen.Model.RegistryServer;
import com.tlgen.factory.RegistryLocalFactory;
import com.tlgen.service.RegistryService;
import com.tlgen.utils.ServerUtils;
import okhttp3.*;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Service
public class RegistryServiceImpl implements RegistryService {

    @Override
    public void notifyAllInstance() {
        for (ConfigServer configServer : ServerUtils.selectServer()) {
            List<RegistryServer> registryList = RegistryLocalFactory.getInstance().getRegistryList();
            // 向其他节点发送需要同步的数据
            if (!Objects.equals(1, configServer.getFlag())) {
                String url = "http://" + configServer.getIp() + ":" + configServer.getPort() + "/registry/receive";
                Call call = new OkHttpClient().newBuilder()
                        .connectTimeout(3, TimeUnit.SECONDS)
                        .readTimeout(3, TimeUnit.SECONDS)
                        .writeTimeout(3, TimeUnit.SECONDS)
                        .build().newCall(new Request.Builder()
                                .url(url)
                                .post(RequestBody.create(
                                        MediaType.parse("application/json; charset=utf-8"),
                                        JSONObject.toJSONString(registryList)))
                                .build());
                // 返回请求结果
                try {
                    Response response = call.execute();
                    assert response.body() != null;
                    System.out.println(response.body().string());
                } catch (IOException e) {
                    System.out.println(url + " 调用失败");
                }
            }
        }
    }

    @Override
    public void pullAllInstance() {
        List<RegistryServer> list = new ArrayList<>();
        List<RegistryServer> registryList = new ArrayList<>();
        for (ConfigServer configServer : ServerUtils.selectServer()) {
            // 向其他节点发送需要同步的数据
            if (!Objects.equals(1, configServer.getFlag())) {
                String url = "http://" + configServer.getIp() + ":" + configServer.getPort() + "/registry/select";
                Call call = new OkHttpClient().newBuilder()
                        .connectTimeout(3, TimeUnit.SECONDS)
                        .readTimeout(3, TimeUnit.SECONDS)
                        .writeTimeout(3, TimeUnit.SECONDS)
                        .build().newCall(new Request.Builder()
                                .url(url)
                                .get()
                                .build());
                // 返回请求结果
                try {
                    Response response = call.execute();
                    assert response.body() != null;
                    JSONObject jsonObject = JSONObject.parseObject(response.body().string());
                    Object o = jsonObject.get("data");
                    if (Objects.nonNull(o)) {
                        JSONArray data = (JSONArray) o;
                        List<com.tlgen.Model.RegistryServer> registryServerList =
                                JSONArray.parseArray(JSONArray.toJSONString(data), com.tlgen.Model.RegistryServer.class);
                        list.addAll(registryServerList);
                    }
                } catch (IOException e) {
                    System.out.println(url + " 调用失败");
                }
            }
        }
        System.out.println("已拉取全量服务列表");
        System.out.println(registryList);
        List<RegistryServer> collect = registryList.stream().distinct().collect(Collectors.toList());
        saveToLocalInstance(collect);
    }


    @Override
    public void saveToLocalInstance(List<RegistryServer> registryList) {
        RegistryLocalFactory.getInstance().setRegistryList(registryList);
    }

    @Override
    public void updateToLocalInstance(List<RegistryServer> registryList) {
        saveToLocalInstance(registryList);
        notifyAllInstance();
    }

    @Override
    public void doRegistry(RegistryServer registryServer) {
        RegistryLocalFactory instance = RegistryLocalFactory.getInstance();
        List<RegistryServer> registryList = instance.getRegistryList();
        registryList.add(registryServer);
        instance.setRegistryList(new ArrayList<>(new HashSet<>(registryList)));
    }

}
